import { decode, encode } from "cbor-x";
import { getUrl } from "./config";
import { type Pro, type ErrInfo, type Hex } from "./model";

async function checkBodyResp<T>(resp: Response) {
	const resp_type = resp.headers.get('resp');
	if (resp_type == null) {
		throw `返回错误:${resp.status} ${resp.statusText}`;
	}
	const body = new Uint8Array(await resp.arrayBuffer());
	if (resp_type == 'ok') {
		return decode(body) as T;
	}
	const info = decode(body) as ErrInfo;
	throw `错误:${info.err_code} ${info.err_msg}`;
}

async function checkEmptyResp(resp: Response) {
	const resp_type = resp.headers.get('resp');
	if (resp_type == null) {
		throw `返回错误:${resp.status} ${resp.statusText}`;
	}
	if (resp_type == 'ok') {
		return;
	}
	const body = new Uint8Array(await resp.arrayBuffer());
	const info = decode(body) as ErrInfo;
	throw `错误:${info.err_code} ${info.err_msg}`;
}

async function doGet<T>(url: string) {
	const resp = await fetch(url, {
		method: 'GET',
	});
	return await checkBodyResp<T>(resp);
}

async function doPost<T, R>(url: string, req: T) {
	const resp = await fetch(url, {
		method: 'POST',
		body: encode(req)
	});
	return await checkBodyResp<R>(resp);
}

async function doPostEmpty<T>(url: string, req: T) {
	const resp = await fetch(url, {
		method: 'POST',
		body: encode(req)
	});
	return await checkEmptyResp(resp);
}

export async function queryPro() {
	return await doGet<Pro[]>(getUrl("/api/pro/query"));
}

export async function createPro(name: string, description: string) {
	return await doPost(getUrl('/api/pro/create'), {
		name,
		description
	}) as number;
}

export async function deletePro(id: number) {
	await doPostEmpty<number>(getUrl('/api/pro/del'), id);
}

export async function createHex(pro_id: number, name: string, version: string, description: string, target: string, body: Uint8Array) {
	await doPostEmpty(getUrl('/api/hex/create'), {
		pro_id,
		name,
		version,
		description,
		target,
		body
	});
}

export async function queryHex(pro_id: number) {
	return await doGet<Hex[]>(getUrl(`/api/hex/query?pro_id=${pro_id}`))
}

export async function deleteHex(id: number) {
	return await doPostEmpty<number>(getUrl('/api/hex/del'), id);
}

